import * as THREE from 'three';
import { gsap } from 'gsap';
import { BaseScene } from './BaseScene.js';

export class ParticleScene extends BaseScene {
    constructor(app, index) {
        super(app, index);
        this.name = '粒子场景';
        // 粒子系统数组
        this.particleSystems = [];
        
        // 场景特定设置
        this.cameraPosition.set(0, 0, 10);
        this.cameraTarget.set(0, 0, 0);
        
        // 粒子参数
        this.baseParticleCount = 2000;
        this.currentParticleCount = this.baseParticleCount;
        
        // 动画参数
        this.timeOffset = 0;
        this.waveAmplitude = 2;
        this.waveFrequency = 0.002;
    }
    
    async createObjects() {
        // 先创建一个简单的测试粒子系统
        this.createSimpleParticleTest();
        
        // 创建主粒子系统
        this.createMainParticleSystem();
        
        // 创建轨道粒子
        this.createOrbitParticles();
        
        // 创建背景星空
        this.createStarField();
        
        // 设置粒子动画
        this.setupParticleAnimations();
    }
    
    createSimpleParticleTest() {
        // 创建一个简单的测试粒子系统，确保粒子可见
        const particleCount = 100;
        const geometry = new THREE.BufferGeometry();
        const positions = new Float32Array(particleCount * 3);
        
        // 在相机前方创建一些简单的粒子
        for (let i = 0; i < particleCount; i++) {
            const i3 = i * 3;
            positions[i3] = (Math.random() - 0.5) * 10;     // x
            positions[i3 + 1] = (Math.random() - 0.5) * 10; // y  
            positions[i3 + 2] = (Math.random() - 0.5) * 10; // z
        }
        
        geometry.setAttribute('position', new THREE.Float32BufferAttribute(positions, 3));
        
        const material = new THREE.PointsMaterial({
            color: 0xff0000, // 红色，容易看见
            size: 10,
            sizeAttenuation: false // 不随距离变化大小
        });
        
        const testParticles = new THREE.Points(geometry, material);
        this.addObject(testParticles);
        
        console.log('测试粒子系统已创建');
    }
    
    createMainParticleSystem() {
        const particleCount = this.currentParticleCount;
        const geometry = new THREE.BufferGeometry();
        
        // 位置数组
        const positions = new Float32Array(particleCount * 3);
        const colors = new Float32Array(particleCount * 3);
        const sizes = new Float32Array(particleCount);
        const velocities = new Float32Array(particleCount * 3);
        
        // 初始化粒子
        for (let i = 0; i < particleCount; i++) {
            const i3 = i * 3;
            
            // 球形分布
            const radius = Math.random() * 5 + 1;
            const theta = Math.random() * Math.PI * 2;
            const phi = Math.acos(Math.random() * 2 - 1);
            
            positions[i3] = radius * Math.sin(phi) * Math.cos(theta);
            positions[i3 + 1] = radius * Math.sin(phi) * Math.sin(theta);
            positions[i3 + 2] = radius * Math.cos(phi);
            
            // 彩虹颜色
            const hue = (i / particleCount) * 360;
            const color = new THREE.Color().setHSL(hue / 360, 0.8, 0.6);
            colors[i3] = color.r;
            colors[i3 + 1] = color.g;
            colors[i3 + 2] = color.b;
            
            // 随机大小
            sizes[i] = Math.random() * 3 + 1;
            
            // 初始速度
            velocities[i3] = (Math.random() - 0.5) * 0.02;
            velocities[i3 + 1] = (Math.random() - 0.5) * 0.02;
            velocities[i3 + 2] = (Math.random() - 0.5) * 0.02;
        }
        
        geometry.setAttribute('position', new THREE.BufferAttribute(positions, 3));
        geometry.setAttribute('color', new THREE.BufferAttribute(colors, 3));
        geometry.setAttribute('size', new THREE.BufferAttribute(sizes, 1));
        
        // 获取粒子纹理
        const texture = this.app.getResourceLoader().getResource('particleTexture');
        
        // 粒子材质 - 使用内置材质以提高稳定性
        const material = new THREE.PointsMaterial({
            size: 5, // 粒子大小
            color: 0xffffff,
            transparent: true,
            blending: THREE.AdditiveBlending,
            vertexColors: true,
            depthWrite: false,
            sizeAttenuation: false, // 先不使用距离衰减，确保可见
            opacity: 0.9
        });
        
        // 如果纹理可用，使用纹理
        if (texture) {
            material.map = texture;
        }
        
        const particles = new THREE.Points(geometry, material);
        particles.userData.velocities = velocities;
        particles.userData.originalPositions = positions.slice();
        
        this.addObject(particles);
        this.particleSystems.push({
            object: particles,
            type: 'main',
            material: material
        });
    }
    
    createOrbitParticles() {
        const orbitCount = 5;
        const particlesPerOrbit = 100;
        
        for (let orbitIndex = 0; orbitIndex < orbitCount; orbitIndex++) {
            const geometry = new THREE.BufferGeometry();
            const positions = new Float32Array(particlesPerOrbit * 3);
            const colors = new Float32Array(particlesPerOrbit * 3);
            
            const radius = 2 + orbitIndex * 1.5;
            const orbitSpeed = 0.01 + orbitIndex * 0.005;
            const orbitColor = new THREE.Color().setHSL(orbitIndex / orbitCount, 1.0, 0.5);
            
            for (let i = 0; i < particlesPerOrbit; i++) {
                const i3 = i * 3;
                const angle = (i / particlesPerOrbit) * Math.PI * 2;
                
                positions[i3] = Math.cos(angle) * radius;
                positions[i3 + 1] = Math.sin(angle) * radius;
                positions[i3 + 2] = (Math.random() - 0.5) * 0.5;
                
                colors[i3] = orbitColor.r;
                colors[i3 + 1] = orbitColor.g;
                colors[i3 + 2] = orbitColor.b;
            }
            
            geometry.setAttribute('position', new THREE.BufferAttribute(positions, 3));
            geometry.setAttribute('color', new THREE.BufferAttribute(colors, 3));
            
            const material = new THREE.PointsMaterial({
                size: 2,
                vertexColors: true,
                transparent: true,
                opacity: 0.8,
                blending: THREE.AdditiveBlending
            });
            
            const orbitParticles = new THREE.Points(geometry, material);
            orbitParticles.userData.radius = radius;
            orbitParticles.userData.speed = orbitSpeed;
            orbitParticles.userData.orbitIndex = orbitIndex;
            
            this.addObject(orbitParticles);
            this.particleSystems.push({
                object: orbitParticles,
                type: 'orbit',
                material: material
            });
        }
    }
    
    createExplosionParticles() {
        // 创建多个小型爆炸效果
        for (let i = 0; i < 3; i++) {
            const particleCount = 200;
            const geometry = new THREE.BufferGeometry();
            const positions = new Float32Array(particleCount * 3);
            const colors = new Float32Array(particleCount * 3);
            const velocities = new Float32Array(particleCount * 3);
            
            const centerX = (Math.random() - 0.5) * 10;
            const centerY = (Math.random() - 0.5) * 10;
            const centerZ = (Math.random() - 0.5) * 10;
            
            for (let j = 0; j < particleCount; j++) {
                const j3 = j * 3;
                
                // 从中心点爆炸
                positions[j3] = centerX;
                positions[j3 + 1] = centerY;
                positions[j3 + 2] = centerZ;
                
                // 爆炸颜色（橙红色系）
                const intensity = Math.random();
                colors[j3] = 1.0;
                colors[j3 + 1] = intensity * 0.5;
                colors[j3 + 2] = intensity * 0.1;
                
                // 爆炸速度
                const speed = Math.random() * 0.1 + 0.05;
                const direction = new THREE.Vector3(
                    Math.random() - 0.5,
                    Math.random() - 0.5,
                    Math.random() - 0.5
                ).normalize();
                
                velocities[j3] = direction.x * speed;
                velocities[j3 + 1] = direction.y * speed;
                velocities[j3 + 2] = direction.z * speed;
            }
            
            geometry.setAttribute('position', new THREE.BufferAttribute(positions, 3));
            geometry.setAttribute('color', new THREE.BufferAttribute(colors, 3));
            
            const material = new THREE.PointsMaterial({
                size: 1,
                vertexColors: true,
                transparent: true,
                opacity: 0.6,
                blending: THREE.AdditiveBlending
            });
            
            const explosion = new THREE.Points(geometry, material);
            explosion.userData.velocities = velocities;
            explosion.userData.life = 0;
            explosion.userData.maxLife = 5000; // 5秒生命周期
            
            this.addObject(explosion);
            this.particleSystems.push({
                object: explosion,
                type: 'explosion',
                material: material
            });
        }
    }
    
    createStarField() {
        const starCount = 500;
        const geometry = new THREE.BufferGeometry();
        const positions = new Float32Array(starCount * 3);
        
        for (let i = 0; i < starCount; i++) {
            const i3 = i * 3;
            
            // 远距离随机分布
            positions[i3] = (Math.random() - 0.5) * 100;
            positions[i3 + 1] = (Math.random() - 0.5) * 100;
            positions[i3 + 2] = (Math.random() - 0.5) * 100;
        }
        
        geometry.setAttribute('position', new THREE.BufferAttribute(positions, 3));
        
        const material = new THREE.PointsMaterial({
            color: 0xffffff,
            size: 0.5,
            transparent: true,
            opacity: 0.3
        });
        
        const stars = new THREE.Points(geometry, material);
        this.addObject(stars);
        
        this.particleSystems.push({
            object: stars,
            type: 'stars',
            material: material
        });
    }
    
    setupParticleAnimations() {
        const mainAnimation = {
            update: ((time) => {
                this.updateMainParticles(time);
                this.updateOrbitParticles(time);
                this.updateExplosionParticles(time);
                this.updateStarField(time);
            }).bind(this) // 绑定正确的this上下文
        };
        
        this.animations.push(mainAnimation);
    }
    
    updateMainParticles(time) {
        const mainSystem = this.particleSystems.find(s => s.type === 'main');
        if (!mainSystem) return;
        
        const particles = mainSystem.object;
        const positions = particles.geometry.attributes.position.array;
        const velocities = particles.userData.velocities;
        const originalPositions = particles.userData.originalPositions;
        
        // 更新粒子位置 - 现在在CPU端计算波动效果
        for (let i = 0; i < positions.length; i += 3) {
            // 添加波动效果
            const waveX = Math.sin(time * this.waveFrequency + originalPositions[i]) * this.waveAmplitude;
            const waveY = Math.cos(time * this.waveFrequency + originalPositions[i + 1]) * this.waveAmplitude;
            const waveZ = Math.sin(time * this.waveFrequency + originalPositions[i + 2]) * this.waveAmplitude;
            
            positions[i] = originalPositions[i] + waveX + velocities[i] * time * 0.1;
            positions[i + 1] = originalPositions[i + 1] + waveY + velocities[i + 1] * time * 0.1;
            positions[i + 2] = originalPositions[i + 2] + waveZ + velocities[i + 2] * time * 0.1;
        }
        
        particles.geometry.attributes.position.needsUpdate = true;
        
        // 添加整体旋转效果
        particles.rotation.y = time * 0.0005;
        particles.rotation.x = time * 0.0003;
    }
    
    updateOrbitParticles(time) {
        const orbitSystems = this.particleSystems.filter(s => s.type === 'orbit');
        
        orbitSystems.forEach(system => {
            const particles = system.object;
            const speed = particles.userData.speed;
            const orbitIndex = particles.userData.orbitIndex;
            
            // 旋转轨道
            particles.rotation.y = time * speed;
            particles.rotation.x = Math.sin(time * 0.001 + orbitIndex) * 0.2;
            particles.rotation.z = Math.cos(time * 0.0015 + orbitIndex) * 0.1;
        });
    }
    
    updateExplosionParticles(time) {
        const explosionSystems = this.particleSystems.filter(s => s.type === 'explosion');
        
        explosionSystems.forEach(system => {
            const particles = system.object;
            const positions = particles.geometry.attributes.position.array;
            const velocities = particles.userData.velocities;
            
            particles.userData.life += 16; // 假设60fps
            
            if (particles.userData.life >= particles.userData.maxLife) {
                // 重置爆炸
                particles.userData.life = 0;
                
                // 重新定位爆炸中心
                const centerX = (Math.random() - 0.5) * 10;
                const centerY = (Math.random() - 0.5) * 10;
                const centerZ = (Math.random() - 0.5) * 10;
                
                for (let i = 0; i < positions.length; i += 3) {
                    positions[i] = centerX;
                    positions[i + 1] = centerY;
                    positions[i + 2] = centerZ;
                }
            } else {
                // 更新爆炸粒子位置
                for (let i = 0; i < positions.length; i += 3) {
                    positions[i] += velocities[i];
                    positions[i + 1] += velocities[i + 1];
                    positions[i + 2] += velocities[i + 2];
                    
                    // 添加重力效果
                    velocities[i + 1] -= 0.001;
                }
            }
            
            particles.geometry.attributes.position.needsUpdate = true;
        });
    }
    
    updateStarField(time) {
        const starSystem = this.particleSystems.find(s => s.type === 'stars');
        if (starSystem) {
            starSystem.object.rotation.y = time * 0.0002;
            starSystem.object.rotation.x = time * 0.0001;
        }
    }
    
    adjustParticleCount(factor) {
        this.currentParticleCount = Math.floor(this.baseParticleCount * factor);
        
        // 调整主粒子系统的透明度
        const mainSystem = this.particleSystems.find(s => s.type === 'main');
        if (mainSystem) {
            // 简化版本：通过调整透明度来模拟粒子数量减少
            const opacity = Math.max(0.3, factor);
            mainSystem.material.opacity = opacity;
        }
        
        // 调整轨道粒子
        const orbitSystems = this.particleSystems.filter(s => s.type === 'orbit');
        orbitSystems.forEach(system => {
            system.material.opacity = Math.max(0.2, factor * 0.8);
        });
        
        console.log(`粒子数量调整为: ${this.currentParticleCount} (因子: ${factor})`);
    }
    
    // 移除自定义着色器，使用Three.js内置PointsMaterial以提高稳定性
}
